using System;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.IO;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Input;
using AvalonEditDemo.Models;
using Microsoft.Win32;
using System.Text;
using CommunityToolkit.Mvvm.ComponentModel;
using CommunityToolkit.Mvvm.Input;
using AvalonEditDemo.Services;

namespace AvalonEditDemo.ViewModels
{
    /// <summary>
    /// 编辑器的主视图模型，负责管理编辑器状态、文档操作和命令执行
    /// 使用CommunityToolkit.Mvvm框架实现MVVM模式
    /// </summary>
    public partial class EditorViewModel : ObservableObject
    {
        private readonly DocumentManager _documentManager;
        private readonly PythonExecutor _pythonExecutor;

        /// <summary>
        /// 获取或设置编辑器当前的文本内容
        /// 通过ObservableProperty特性自动实现通知属性更改功能
        /// </summary>
        [ObservableProperty]
        private string _editorText = string.Empty;

        /// <summary>
        /// 获取或设置输出区域的文本内容
        /// 用于显示Python代码执行结果和错误信息
        /// </summary>
        [ObservableProperty]
        private string _outputText = string.Empty;

        /// <summary>
        /// 获取或设置状态栏显示的消息
        /// </summary>
        [ObservableProperty]
        private string _statusMessage = string.Empty;

        /// <summary>
        /// 获取或设置当前活动的文档
        /// </summary>
        [ObservableProperty]
        private DocumentInfo? _activeDocument;

        /// <summary>
        /// 获取或设置表示是否正在执行Python代码的标志
        /// </summary>
        [ObservableProperty]
        private bool _isExecuting;

        /// <summary>
        /// 获取所有打开的文档列表
        /// </summary>
        public ObservableCollection<DocumentInfo> OpenDocuments => _documentManager.OpenDocuments;

        /// <summary>
        /// 获取应用程序窗口标题，根据当前活动文档的状态动态生成
        /// </summary>
        public string WindowTitle => ActiveDocument == null 
            ? "Python Editor" 
            : $"Python Editor - {ActiveDocument.FileName}{(ActiveDocument.IsDirty ? "*" : "")}";

        /// <summary>
        /// 初始化EditorViewModel的新实例
        /// </summary>
        public EditorViewModel()
        {
            _documentManager = new DocumentManager();
            _pythonExecutor = new PythonExecutor();
            ActiveDocument = _documentManager.ActiveDocument;
        }

        /// <summary>
        /// 当编辑器文本发生变化时调用
        /// 更新文档状态并标记为已修改
        /// </summary>
        /// <param name="value">新的编辑器文本</param>
        partial void OnEditorTextChanged(string value)
        {
            if (ActiveDocument != null)
            {
                ActiveDocument.Content = value;
                _documentManager.MarkDocumentDirty(ActiveDocument);
                OnPropertyChanged(nameof(WindowTitle));
                
                // 更新代码补全服务中的当前文本
                Services.CodeCompletionService.Instance?.UpdateEditorText(value);
            }
        }

        /// <summary>
        /// 当活动文档发生变化时调用
        /// 更新编辑器文本和窗口标题
        /// </summary>
        /// <param name="value">新的活动文档</param>
        partial void OnActiveDocumentChanged(DocumentInfo? value)
        {
            EditorText = value?.Content ?? string.Empty;
            OnPropertyChanged(nameof(WindowTitle));
        }

        /// <summary>
        /// 创建新文档的命令方法
        /// 使用RelayCommand特性自动生成相应的命令
        /// </summary>
        [RelayCommand]
        private void New()
        {
            ActiveDocument = _documentManager.NewDocument();
            StatusMessage = "新建文档";
        }

        /// <summary>
        /// 分析当前编辑器中的代码，更新代码补全提示
        /// </summary>
        [RelayCommand]
        private void AnalyzeCode()
        {
            if (string.IsNullOrWhiteSpace(EditorText))
            {
                StatusMessage = "没有代码可分析";
                return;
            }
            
            try
            {
                // 手动触发代码分析
                Services.CodeCompletionService.Instance?.UpdateEditorText(EditorText);
                StatusMessage = "代码分析完成，代码补全已更新";
            }
            catch (Exception ex)
            {
                StatusMessage = $"代码分析失败: {ex.Message}";
            }
        }

        /// <summary>
        /// 打开文件的命令方法
        /// </summary>
        [RelayCommand]
        private async Task OpenAsync()
        {
            var dialog = new OpenFileDialog
            {
                Filter = "Python文件 (*.py)|*.py|所有文件 (*.*)|*.*",
                Title = "打开Python文件"
            };

            if (dialog.ShowDialog() == true)
            {
                try
                {
                    var document = await _documentManager.OpenFileAsync(dialog.FileName);
                    ActiveDocument = document;
                    StatusMessage = $"已打开: {ActiveDocument.FilePath}";
                }
                catch (Exception ex)
                {
                    StatusMessage = $"打开文件失败: {ex.Message}";
                }
            }
        }

        /// <summary>
        /// 保存当前文档的命令方法
        /// 如果是未命名文档，则调用SaveAs
        /// </summary>
        [RelayCommand(CanExecute = nameof(CanSave))]
        private async Task SaveAsync()
        {
            if (ActiveDocument!.IsUntitled)
            {
                await SaveAsAsync();
                return;
            }

            await SaveDocumentInternalAsync(ActiveDocument.FilePath);
        }

        /// <summary>
        /// 判断是否可以执行保存命令
        /// </summary>
        /// <returns>如果有活动文档，则返回true</returns>
        private bool CanSave() => ActiveDocument != null;

        /// <summary>
        /// 另存为命令方法，显示保存对话框
        /// </summary>
        [RelayCommand(CanExecute = nameof(CanSave))]
        private async Task SaveAsAsync()
        {
            var dialog = new SaveFileDialog
            {
                Filter = "Python文件 (*.py)|*.py|所有文件 (*.*)|*.*",
                Title = "保存Python文件"
            };

            if (dialog.ShowDialog() == true)
            {
                await SaveDocumentInternalAsync(dialog.FileName);
            }
        }

        /// <summary>
        /// 内部方法，执行实际的文件保存操作
        /// </summary>
        /// <param name="filePath">要保存到的文件路径</param>
        private async Task SaveDocumentInternalAsync(string filePath)
        {
            try
            {
                bool result = await _documentManager.SaveDocumentAsync(ActiveDocument!, filePath);
                if (result)
                {
                    StatusMessage = $"已保存: {ActiveDocument!.FilePath}";
                    OnPropertyChanged(nameof(WindowTitle));
                }
                else
                {
                    StatusMessage = "保存文件失败";
                }
            }
            catch (Exception ex)
            {
                StatusMessage = $"保存文件失败: {ex.Message}";
            }
        }

        /// <summary>
        /// 关闭当前文档的命令方法
        /// 如果文档有未保存的更改，会提示用户保存
        /// </summary>
        [RelayCommand(CanExecute = nameof(CanSave))]
        private void Close()
        {
            if (ActiveDocument!.IsDirty)
            {
                var result = MessageBox.Show(
                    $"是否保存对 {ActiveDocument.FileName} 的更改?",
                    "Python编辑器",
                    MessageBoxButton.YesNoCancel);

                switch (result)
                {
                    case MessageBoxResult.Yes:
                        SaveCommand.Execute(null);
                        break;
                    case MessageBoxResult.Cancel:
                        return;
                }
            }

            _documentManager.CloseDocument(ActiveDocument);
            ActiveDocument = _documentManager.ActiveDocument;
        }

        /// <summary>
        /// 运行Python代码的命令方法
        /// </summary>
        [RelayCommand(CanExecute = nameof(CanRun))]
        public async Task RunAsync()
        {
            try
            {
                IsExecuting = true;
                
                // 检查是否有代码要执行
                if (string.IsNullOrWhiteSpace(EditorText))
                {
                    OutputText = "请先输入一些Python代码再运行";
                    StatusMessage = "没有代码可执行";
                    return;
                }

                // 创建临时文件
                string tempFile = Path.GetTempFileName() + ".py";
                await File.WriteAllTextAsync(tempFile, EditorText, Encoding.UTF8);
                    
                // 显示代码预览，帮助调试缩进问题
                StringBuilder codePreview = new StringBuilder();
                codePreview.AppendLine("准备执行以下Python代码:");
                codePreview.AppendLine("------------------------");
                    
                // 添加行号
                string[] codeLines = EditorText.Split('\n');
                for (int i = 0; i < codeLines.Length; i++)
                {
                    codePreview.AppendLine($"{i + 1,3}: {codeLines[i]}");
                }
                codePreview.AppendLine("------------------------");
                System.Diagnostics.Debug.WriteLine(codePreview.ToString());

                // 执行Python文件
                var result = await _pythonExecutor.ExecuteWithSystemPythonAsync(EditorText);

                if (result.Success)
                {
                    OutputText = result.Output;
                    StatusMessage = $"执行完成，耗时: {result.ExecutionTime.TotalMilliseconds:F0}ms";
                }
                else
                {
                    OutputText = $"执行错误:\n{result.Error}\n\n{result.Output}\n\n耗时: {result.ExecutionTime.TotalMilliseconds:F0}ms";
                    StatusMessage = "执行出现错误";
                }
            }
            catch (Exception ex)
            {
                OutputText = $"执行异常: {ex.Message}";
                StatusMessage = "执行出现异常";
            }
            finally
            {
                IsExecuting = false;
            }
        }

        /// <summary>
        /// 判断是否可以执行运行命令
        /// </summary>
        /// <returns>如果当前没有正在执行的代码，则返回true</returns>
        private bool CanRun() => !IsExecuting;
    }
} 